package ufile

import (
	"crypto/md5"
	"io"
	"fmt"
	"os"
	"strings"
	"runtime"
	"net/http"
	"io/ioutil"
	"crypto/tls"
)

/**
 基于文件创建其对应的dir
 */
func CreateDirByFile(destFile string, perm os.FileMode) error {
	var dirName string

	if runtime.GOOS == "windows" {
		lastIndex := strings.LastIndex(destFile, "\\")
		dirName = destFile[0: lastIndex]
	} else if runtime.GOOS == "linux" || runtime.GOOS == "darwin" {
		lastIndex := strings.LastIndex(destFile, "/")
		dirName = destFile[0: lastIndex]
	}

	err := os.MkdirAll(dirName, perm)

	return err
}

/**
 文件下载,同时支持http和https方式
 */
func DownloadFile(url string, destFile string) error {

	var err error
	err = CreateDirByFile(destFile, 0744)
	if err != nil {
		return err
	}

	var resp *http.Response
	if strings.HasPrefix(url, "https://") {
		// https方式下载文件
		// 创建tls的不校验服务端的证书的client
		tr := &http.Transport{
			TLSClientConfig: &tls.Config{ InsecureSkipVerify: true },
		}
		client := &http.Client{Transport: tr}

		resp, err = client.Get(url)

	} else if strings.HasPrefix(url, "http://") {
		// http方式下载文件
		resp, err = http.Get(url)
	} else {
		return fmt.Errorf("file url error.")
	}

	if err != nil {
		return err
	}
	defer resp.Body.Close()

	htmlData, _ := ioutil.ReadAll(resp.Body)

	// 写文件
	err = ioutil.WriteFile(destFile, htmlData, 0744)
	if err != nil {
		return err
	}

	return nil
}

/**
 计算文件的md5值
 */
func GetFileMd5(fileName string) string {
	fileStream, err := os.Open(fileName)
	if err != nil {
		return ""
	}
	defer fileStream.Close()

	md5h := md5.New()
	io.Copy(md5h, fileStream)

	return fmt.Sprintf("%x", md5h.Sum(nil))
}

/**
 判断指定路径的文件是否存在
 */
func FileExists(fileName string) bool {
	_, err := os.Stat(fileName)
	if err == nil {
		return true
	}

	if os.IsNotExist(err) {
		return false
	}

	return false
}

/**
 修改文件的mod值
 */
func ChangeFileMode(fileName string, mode os.FileMode) error {
	if FileExists(fileName) == false {
		return fmt.Errorf("file no exist: %s", fileName)
	}

	err := os.Chmod(fileName, mode)
	if err != nil {
		return err
	}

	return nil
}